/*
		ServEngine framework library
		A library to fast develop JEE online applications
	
		Copyright 2008 José Ignacio de Córdoba Álvaro

		Licensed under the Apache License, Version 2.0 (the "License");
		you may not use this file except in compliance with the License.
		You may obtain a copy of the License at

				http://www.apache.org/licenses/LICENSE-2.0

		Unless required by applicable law or agreed to in writing, software
		distributed under the License is distributed on an "AS IS" BASIS,
		WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
		See the License for the specific language governing permissions and
		limitations under the License.
	
		Jose Ignacio de Cordoba Alvaro
		http://ignacio.decordoba.com
*/

package com.servengine.user;

import com.servengine.Cleaner;

import com.servengine.portal.Portal;
import com.servengine.struts.AdminServiceAction;
import com.servengine.util.MailRelay;
import com.servengine.util.ServletContextUtils;

import java.beans.Introspector;
import java.beans.PropertyDescriptor;

import java.io.BufferedReader;
import java.io.IOException;

import java.io.InputStreamReader;

import java.io.StringReader;

import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import java.util.TreeSet;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import javax.transaction.UserTransaction;

import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionForward;
import org.apache.struts.action.ActionMapping;

import org.apache.commons.beanutils.PropertyUtils;

/**
 * This struts action class groups generic admin actions not related to any ActionForm in this module.
 * @see Actions
 * @see UserActions
 * @see UserAdminActions
 * @see UserActionForm
 */
public class AdminActions extends com.servengine.struts.ClientAction implements AdminServiceAction
{
	private static org.apache.commons.logging.Log log=org.apache.commons.logging.LogFactory.getLog(AdminActions.class.getName());

	public void initAction(javax.naming.Context context)
	{
		log.info(getClass().getName()+" initialized");
	}

/*	public ActionForward index(ActionMapping mapping, ActionForm form, HttpServletRequest request,
														HttpServletResponse response) throws IOException, ServletException
	{
		lastUsers(mapping, form, request, response);
		if (getErrors(request).size()>0)
			return mapping.findForward("error");
		return mapping.findForward("index");
	}*/

	public ActionForward unspecified(ActionMapping mapping, ActionForm form, HttpServletRequest request,
																	HttpServletResponse response) throws IOException, ServletException
	{
		return preferences(mapping, form, request, response);
	}

	public ActionForward users(ActionMapping mapping, ActionForm form, HttpServletRequest request,
																HttpServletResponse response) throws IOException, ServletException
	{
		try
		{
		  UserSessionSBean userSession=getUserSession(request);
			TreeSet<User> users=new TreeSet<User>(); // TODO Cambiar por comparador de fechas
			users.addAll(usermanager.getUsers(userSession.getPortalid()));
			request.getSession().setAttribute("users", users);
		  return mapping.findForward("success");
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
			saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
	}
	public ActionForward lastUsers(ActionMapping mapping, ActionForm form, HttpServletRequest request,
																HttpServletResponse response) throws IOException, ServletException
	{
//		UsersActionForm usersForm=(UsersActionForm)form;
		UserSessionSBean userSession=getUserSession(request);
		try
		{
			TreeSet<User> lastusers=new TreeSet<User>(); // TODO Cambiar por comparador de fechas
			lastusers.addAll(usermanager.getLastUsers(userSession.getPortalid()));
			request.getSession().setAttribute("users", lastusers);
			//request.setAttribute("newUserCount",
			//									usermanager.getNewusercount(userSession.getPortalid(), userSession.getLastLogin()==null?userSession.getCreationdate():
			//																											userSession.getLastLogin()));
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
		  saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
		return mapping.findForward("success");
	}

/*	public ActionForward getLastusers(ActionMapping mapping, ActionForm form, HttpServletRequest request,
																	 HttpServletResponse response) throws IOException, ServletException
	{
		UserActionForm user=getUser(request);
	  DynaActionForm users=(DynaActionForm)form;
		try
		{
			int howmanyuserstoreturn=
				request.getParameter("howmanyuserstoreturn")==null?20:Integer.parseInt(request.getParameter("howmanyuserstoreturn"));
			TreeSet lastusers=new TreeSet(); // Cambiar por comparador de fechas
			lastusers.addAll(usermanager.getLastusers(user.getPortalid(), howmanyuserstoreturn));
			users.set("users", lastusers);
			request.setAttribute("newusercount", usermanager.getNewusercount(user.getPortalid(), user.getLastLogin()));
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
			ActionErrors errors=new ActionErrors();
			errors.add("error", new ActionMessage(e.getClass().getName(), e.getMessage()));
			saveErrors(request, errors);
			return mapping.findForward("error");
		}
		return mapping.findForward("lastusers");
	}*/

	public ActionForward removeUsers(ActionMapping mapping, ActionForm form, HttpServletRequest request,
																	HttpServletResponse response) throws IOException, ServletException
	{
		try
		{
		  UserSessionSBean userSession=getUserSession(request);
			HashSet<Cleaner> cleaners=new HashSet<Cleaner>(); // TODO Calcular los Cleaners
/*			for (ComponentSBean comp: statelessutils.getServiceclientcomponents())
				try
				{
					if (comp.getServiceName().equals("cleaner"))//FIXME Esto esta mal, se están pasando mal los parámetros a newInstance.
					{
						Class[] constructorparameters=new Class[]{ Class.forName("javax.servlet.ServletContext") };
						com.servengine.Cleaner cleaner=
							(com.servengine.Cleaner)(Class.forName(comp.getClassname()).getConstructor(constructorparameters).newInstance(constructorparameters));
						cleaners.add(cleaner);
					}
				} catch (ClassNotFoundException e)
				{
					servletcontext.log("IMPORTANTE: No existe la clase: "+e+"/"+e.getMessage());
				} catch (java.lang.NoClassDefFoundError e)
				{
					servletcontext.log("IMPORTANTE: No existe la clase: "+e+"/"+e.getMessage());
				} catch (InstantiationException e)
				{
					servletcontext.log("removeUser():ERROR(IE),"+e.getMessage());
				} catch (IllegalAccessException e)
				{
					servletcontext.log("removeUser():ERROR(IAE),"+e.getMessage());
				}*/
			if (request.getParameterValues("userid")!=null)
			{
				Collection<User> usersCollection = (Collection<User>)request.getSession().getAttribute("users");
				TreeSet<User> newUsersCollection = usersCollection==null?new TreeSet<User>():new TreeSet<User>(usersCollection);
				for (String userid: request.getParameterValues("userid"))
				{
					if (userid.equals(userSession.getUserid()))
						throw new IllegalArgumentException("CantRemoveYourUser");
					usermanager.removeUser(userSession.getPortalid(), userid);
					for (Cleaner cleaner: cleaners)
						cleaner.userRemoved(userSession.getPortalid(), userid);
					if (usersCollection!=null)
						for (User userdto: usersCollection)
							if (userdto.getUserid().equals(userid))
								newUsersCollection.remove(userdto);
				  logManager.log(userSession.getPortalid(),userSession.getUser().getId(),"user","AdminActions","removeUsers",userid,request.getRemoteAddr());
				}
			  request.getSession().setAttribute("users",newUsersCollection);
			}
		  return mapping.findForward("success");
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
		  saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
	}

	/**
	 * Performs a user search. Can receive extra searchparameters as a Set of java.util.Map.Entry's request attribute.
	 * @param mapping
	 * @param form
	 * @param request
	 * @param response
	 * @return
	 * @throws IOException
	 * @throws ServletException
	 */
	public ActionForward search(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{
	  try
	  {
	    UserSessionSBean userSession=getUserSession(request);
	    Map<String, Object> searchParameters=new HashMap<String, Object>();
			
	    for (PropertyDescriptor propertyDescriptor: Introspector.getBeanInfo( form.getClass()).getPropertyDescriptors())
				try
				{
					Object object = propertyDescriptor.getReadMethod().invoke(form,null);
					if (object!=null)
						searchParameters.put(propertyDescriptor.getName(),object);
				} catch (Throwable e)
				{
					if (log.isDebugEnabled())
						log.debug(e+": "+propertyDescriptor.getName());
				}
		/*
			if (form instanceof com.servengine.struts.ValidatorForm)
	    {
			  UsersActionForm usersForm = (UsersActionForm)form;
			  if (usersForm.getUserid()!=null)
			    searchParameters.put("id", usersForm.getUserid());
			  if (usersForm.getEmail()!=null)
			    searchParameters.put("email", usersForm.getEmail());
			  if (usersForm.getFirstName()!=null)
			    searchParameters.put("firstname", usersForm.getFirstName());
			  if (usersForm.getLastName()!=null)
			    searchParameters.put("lastname",usersForm.getLastName());
			  if (usersForm.getRoleId()!=null)
			    searchParameters.put("roleId", usersForm.getRoleId());
			  if (usersForm.getSearchString()!=null)
			    searchParameters.put("searchstring", usersForm.getSearchString());
			  if (usersForm.getCreatedFrom()!=null)
			    searchParameters.put("creationDateFrom", usersForm.getCreatedFrom());
			  if (usersForm.getCreatedTo()!=null)
			    searchParameters.put("creationDateTo", usersForm.getCreatedTo());
			    //TODO terminar los criterios de búsqueda
			}			
			else
			{
			  UsersActionForm usersForm=(UsersActionForm)form;
				if (usersForm.getUserid()!=null&&((String)usersForm.getUserid()).length()>0)
					searchParameters.put("id", (String)usersForm.getUserid());
				if (usersForm.getEmail()!=null&&((String)usersForm.getEmail()).length()>0)
					searchParameters.put("email", (String)usersForm.getEmail());
				if (usersForm.getFirstName()!=null&&((String)usersForm.getFirstName()).length()>0)
					searchParameters.put("firstname", (String)usersForm.getFirstName());
				if (usersForm.getLastName()!=null&&((String)usersForm.getLastName()).length()>0)
					searchParameters.put("lastname", (String)usersForm.getLastName());
				if (usersForm.getRoleId()!=null)
					searchParameters.put("roleIds", usersForm.getRoleId());//FIXME Resolver esto en el manager
				if (usersForm.getSearchString()!=null && ((String)usersForm.getSearchString()).length()>0)
					searchParameters.put("searchstring", (String)usersForm.getSearchString());
			}*/
	    request.getSession().setAttribute("users", new TreeSet<User>(usermanager.searchUsers(userSession.getPortalid(), searchParameters)));
	    return mapping.findForward("success");
	  } catch (Throwable e)
	  {
	    log.error(e.getMessage(), e);
	    saveErrors(request,getErrorsFromException(e));
	    return mapping.findForward("error");
	  }
	}

	public ActionForward searchUsersWithNoRole(ActionMapping mapping, ActionForm form, HttpServletRequest request,
														 HttpServletResponse response) throws IOException, ServletException
	{
		try
		{
			UserSessionSBean userSession=getUserSession(request);
			request.getSession().setAttribute("users", new TreeSet<User>(usermanager.getUsersByRoleIds(userSession.getPortalid(), null)));
	    return mapping.findForward("success");
	  } catch (Throwable e)
	  {
	    log.error(e.getMessage(), e);
	    saveErrors(request,getErrorsFromException(e));
	    return mapping.findForward("error");
	  }
	}
	
	public ActionForward setRolesToFoundUsers(ActionMapping mapping, ActionForm form, HttpServletRequest request,
														 HttpServletResponse response) throws IOException, ServletException
	{
		try
		{
	    UserSessionSBean userSession=getUserSession(request);
	    if (request.getSession().getAttribute("users")!=null && request.getParameterValues("roleid")!=null)
	    {
				Set<Role> roles = new HashSet<Role>();
				for (String roleid: request.getParameterValues("roleid"))
					roles.add(usermanager.getRole(userSession.getPortalid(),roleid));
				for (User user: (Collection<User>)request.getSession().getAttribute("users"))
					user.setRoles(roles);//FIXME Que se añadan a los que ya tiene.
					// TODO ¿No hace falta persistir?
			}
	    return mapping.findForward("success");
	  } catch (Throwable e)
	  {
	    log.error(e.getMessage(), e);
	    saveErrors(request,getErrorsFromException(e));
	    return mapping.findForward("error");
	  }
	}
 
/*	public ActionForward getSearchusers(ActionMapping mapping, ActionForm form, HttpServletRequest request,
																		 HttpServletResponse response) throws IOException, ServletException
	{
		UserActionForm user=getUser(request);
		try
		{
			Map<String, Object> searchparameters=new HashMap<String, Object>();
			if (request.getAttribute("searchparameters")!=null)
				for (java.util.Map.Entry<String, Object> searchentry:
				 (java.util.Set<java.util.Map.Entry<String, Object>>)request.getAttribute("searchparameters"))
					searchparameters.put(searchentry.getKey(), searchentry.getValue());
			if (request.getParameter("id")!=null&&request.getParameter("id").length()>0)
				searchparameters.put("id", request.getParameter("id"));
			if (request.getParameter("email")!=null&&request.getParameter("email").length()>0)
				searchparameters.put("email", request.getParameter("email"));
			if (request.getParameter("firstname")!=null&&request.getParameter("firstname").length()>0)
				searchparameters.put("firstname", request.getParameter("firstname"));
			if (request.getParameter("lastname")!=null&&request.getParameter("lastname").length()>0)
				searchparameters.put("lastname", request.getParameter("lastname"));
			if (request.getParameter("rolepkey")!=null&&request.getParameter("rolepkey").length()>0)
				searchparameters.put("rolepkey", new Integer(request.getParameter("rolepkey")));

			Date lastaccess=getDatefromdaymonthyear(request, "lastaccessdate");
			if (lastaccess!=null)
				searchparameters.put("lastaccessdate", lastaccess);
			Date creation=getDatefromdaymonthyear(request, "creationdate");
			if (creation!=null)
				searchparameters.put("creationdate", creation);

			if (request.getParameter("searchstring")!=null&&request.getParameter("searchstring").length()>0)
				searchparameters.put("searchstring", request.getParameter("searchstring"));

			request.getSession().setAttribute("users", new TreeSet<UserSBean>(usermanager.getUsers(user.getPortalid(), searchparameters)));
			request.getSession().setAttribute("searchparameters", searchparameters.entrySet());
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
			ActionErrors errors=new ActionErrors();
			errors.add("error", new ActionMessage(e.getClass().getName(), e.getMessage()));
			saveErrors(request, errors);
			return mapping.findForward("error");
		}
		return mapping.findForward("searchedusers");
	}*/

	/*	public ActionForward browsesearch(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException,ServletException
	{
		UserSBean user = (UserSBean)request.getAttribute("user");
		try
		{
			
		} catch (Throwable e)
		{
			log.error(e.getMessage(),e);
			ActionErrors errors = new ActionErrors();
			errors.add("error",new ActionMessage(e.getClass().getName(),e.getMessage()));
			saveErrors(request,errors);
			return mapping.findForward("error");
		}
		return mapping.findForward("lastusers");
	}*/

	/*	public ActionForward getRoles(ActionMapping mapping, ActionForm form, HttpServletRequest request,
		HttpServletResponse response) throws IOException, ServletException
	{
	  UserActionForm user = getUser(request);
		try
		{
			request.setAttribute("roles", usermanager.getRoles(user.getPortalid()));
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
			ActionErrors errors = new ActionErrors();
			errors.add("error", new ActionMessage(e.getClass().getName(), e.getMessage()));
			saveErrors(request, errors);
			return mapping.findForward("error");
		}
		return mapping.findForward("roles");
	}
*/

	public ActionForward preferences(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{
		try
		{
		  UserSessionSBean userSession=getUserSession(request);
		  PreferencesForm preferences=(PreferencesForm)form;
			preferences.setHasGuestUser(usermanager.hasGuestUser(userSession.getPortalid()));
			preferences.setSessionRememberDays(userSession.getPortal().getSessionRememberDays());
			preferences.setNewUserNotify(userSession.getPortal().isNewUserNotification());
			preferences.setSelfSignUp(userSession.getPortal().isUserSelfSignup());
			preferences.setRequiresSignUpConfirmation(userSession.getPortal().isRequiresSignupConfirmation());
		  preferences.setExtraUserdataFields(userSession.getPortal().getExtraUserdataFields());
		  return mapping.findForward("success"); // Cuidado, preferencias de usuario
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
		  saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
	}

	public ActionForward storePreferences(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{
		try
		{
		  UserSessionSBean userSession=getUserSession(request);
		  PreferencesForm preferences=(PreferencesForm)form;
			Portal portal = portalmanager.getPortal(userSession.getPortalid());
			portal.setSessionRememberDays(preferences.getSessionRememberDays());
			usermanager.setGuestUser(userSession.getPortal(),preferences.isHasGuestUser());
			portal.setNewUserNotification(preferences.isNewUserNotify());
			portal.setUserSelfSignup(preferences.isSelfSignUp());
			portal.setRequiresSignupConfirmation(preferences.isRequiresSignUpConfirmation());
		  for (ExtraUserdataField field: portal.getExtraUserdataFields())
			{
				ExtraUserdataField formField = preferences.getExtraUserdataField(""+field.getId());//String por ser un campo mapeado para JSTL.
				formField.setPortal(portal);//Se pierde por la chapuza de meter el Field en el ActionForm
			  PropertyUtils.copyProperties(field,formField);
			}
			if (preferences.getNewExtraUserdataFieldName()!=null && preferences.getNewExtraUserdataFieldName().length()>0)
		  {
				if (portal.getExtraUserdataFieldsMap().keySet().contains(preferences.getNewExtraUserdataFieldName()))
					throw new IllegalArgumentException("error.FieldNameExists");
				portal.getExtraUserdataFields().add(new ExtraUserdataField(portal,preferences.getNewExtraUserdataFieldName()));
				preferences.setNewExtraUserdataFieldName(null);
			}
			portalmanager.persist(portal);
		  if (preferences.getRemoveExtraUserdataFieldId()!=null)
			  portalmanager.removeExtraUserdataFields(portal.getId(),preferences.getRemoveExtraUserdataFieldId());
			getUserSession(request).refresh(portalmanager.getPortal(userSession.getPortalid()));
		  logManager.log(userSession.getPortalid(),userSession.getUser().getId(),"user","AdminActions","storePreferences",null,request.getRemoteAddr());
		  return preferences(mapping,form,request,response);
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
		  saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
	}
	//		

	public ActionForward onlineUserSessions(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{
		try
		{
			request.getSession().setAttribute("onlineUserSessions", getUserSession(request).getOnlineUserSessions());
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
		  saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
		return mapping.findForward("onlineUserSessions"); // Cuidado, preferencias de usuario
	}

	public ActionForward lastUserSessions(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{
		try
		{
		  UserSessionSBean userSession=getUserSession(request);
		  request.getSession().setAttribute("lastUserSessions", new TreeSet<UserSession>(usermanager.getLastUserSessions(userSession.getPortalid())));
		  return mapping.findForward("lastUserSessions");
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
		  saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
	}

	public ActionForward searchLastUserSessions(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{
		try
		{
		  UserSessionSBean userSession=getUserSession(request);
			UsersActionForm usersForm = (UsersActionForm) form;
			request.getSession().setAttribute("lastUserSessions", new TreeSet<UserSession>(usermanager.getLastUserSessionsBySearchString(userSession.getPortalid(),usersForm.getSearchString())));
		  return mapping.findForward("lastUserSessions");
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
			saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
	}

	public ActionForward invalidateUserSessions(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{
		try
		{
			UsersActionForm usersForm = (UsersActionForm) form;
			if (usersForm.getHttpSessionId()!=null)
			{
				UserSessionSBean userSession=getUserSession(request);
				ServletContextUtils servletContextUtils= getServletContextUtils();
				for (String id: usersForm.getHttpSessionId())
				{
					if (!userSession.getHttpSession().getId().equals(id))
					{
						String userid = servletContextUtils.disconnectSession(userSession.getPortalid(),id);
						logManager.log(userSession.getPortalid(),userSession.getUser().getId(),"user","AdminActions","invalidateUserSessions",userid+","+id,request.getRemoteAddr());
					}
				}
			}
			return onlineUserSessions(mapping,form,request,response);
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
			saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
	}
	
	public ActionForward multiMail(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{
	  UserTransaction ut = null;
	  try
	  {
	    ut = getUserTransaction();
	    UserSessionSBean userSession=getUserSession(request);
	    UsersActionForm usersForm = (UsersActionForm) form;
	    Collection<User> users = usersForm.getRoleId()==null || usersForm.getRoleId().length==0 ?
				usermanager.getUsers(userSession.getPortalid()) :
				usermanager.getUsersByRoleIds(userSession.getPortalid(),usersForm.getRoleId());
			MailRelay mailRelay = getMailRelay();
			String portalEmail = portalmanager.getEmail(userSession.getPortalid()).toString();
			for (User user: users)
				try
				{
					mailRelay.send(portalEmail,user.getEmail(),usersForm.getMessageSubject(),usersForm.getMessageTextBody(),usersForm.getMessageHtmlBody());
				} catch (Throwable e)
				{
					if (log.isDebugEnabled())
					  log.error(user.getUserid()+"@"+user.getPortalid()+": ",e);
					else
						log.error(user.getUserid()+"@"+user.getPortalid()+": "+e);
				}					
			ut.commit();
	    return mapping.findForward("multiMail");
	  } catch (Throwable e)
	  {
	    try
	    {
	      ut.rollback();
	    } catch (Exception e2)
	    {
	      log.error(e.getMessage(),e2);
	    }
	    log.error(e.getMessage(), e);
	    saveErrors(request,getErrorsFromException(e));
	    return mapping.findForward("error");
	  }
	}
	 /*public ActionForward multiMailForm(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	 {
		 return mapping.findForward("multiMailForm");
	 }
	public ActionForward importUsersForm(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{
		return mapping.findForward("importUsersForm");
	}*/
	
	public ActionForward importUsersTest(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{
	  try
	  {
	    UserSessionSBean userSession=getUserSession(request);
	    UsersActionForm users = (UsersActionForm)form;
	    BufferedReader reader = new BufferedReader(new InputStreamReader((users.getImportFile()).getInputStream()
			,users.getCharsetName()==null || users.getCharsetName().length()==0?"utf-8":users.getCharsetName()));
	    String line=null;//id, firstname, lastname, lastname2, email, password, [extra fields alfabéficamente]
			TreeSet<ExtraUserdataField> extraFields = new TreeSet<ExtraUserdataField>(userSession.getPortal().getExtraUserdataFields());
			Collection<User> usersTest = new ArrayList<User>();
	    int errorCount=0;
			while ((line=reader.readLine())!=null)
				try
				{
					usersTest.add(getUserFromLine(userSession.getPortal(),line.split(",",-1),extraFields));
				} catch (Throwable e)
				{
					if (log.isDebugEnabled())
						log.debug(e.getMessage(),e);
					errorCount++;
				}
	    request.setAttribute("extraFields",extraFields);
			request.getSession().setAttribute("importUsersFormFile",users.getImportFile());
			request.setAttribute("users",usersTest);
			request.setAttribute("errorCount",errorCount);
			return mapping.findForward("importUsersTest");
	  } catch (Throwable e)
	  {
	    log.error(e.getMessage(), e);
	    saveErrors(request,getErrorsFromException(e));
	    return mapping.findForward("error");
	  }
	}
	
	public ActionForward importUsers(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{ //TODO Premium
		try
		{
			UserSessionSBean userSession=getUserSession(request);
		  UsersActionForm users = (UsersActionForm)form;
			BufferedReader reader = new BufferedReader(new InputStreamReader(((org.apache.struts.upload.FormFile)request.getSession().getAttribute("importUsersFormFile")).getInputStream()
			,users.getCharsetName()==null || users.getCharsetName().length()==0?"utf-8":users.getCharsetName()));
			String line=null;//id, firstname, lastname, lastname2, email, password, [extra fields alfabéficamente]
			TreeSet<ExtraUserdataField> extraFields = new TreeSet<ExtraUserdataField>(userSession.getPortal().getExtraUserdataFields());
			Set<Role> roles = new HashSet<Role>();
			roles.addAll(usermanager.getNewUserRoles(userSession.getPortalid()));
		  int errorCount=0;
			String errors = "";
			while ((line=reader.readLine())!=null)
			{
			  try
			  {
					String[] fields = line.split(",",-1);
					User user = getUserFromLine(userSession.getPortal(),fields,extraFields);
					user.setRoles(roles);
					usermanager.persist(user,null);
					if (fields.length>5 && fields[5]!=null && fields[5].length()>0)
						usermanager.changeUserPassword(userSession.getPortalid(),user.getUserid(),fields[5].trim());
			  } catch (Throwable e)
			  {
					errors+=line+"\n";
					errors+=e.getMessage()+"\n";
			    if (log.isDebugEnabled())
			      log.debug(e.getMessage());
			    errorCount++;
			  }
			}
		  logManager.log(userSession.getPortalid(),userSession.getUser().getId(),"user","AdminActions","importUsers",null,request.getRemoteAddr());
			request.getSession().removeAttribute("importUsersFormFile");
			request.getSession().setAttribute("importUsersErrors",errors);
		  request.setAttribute("errorCount",errorCount);
			return mapping.findForward("importUsers");
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
			saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
	}
	
	protected User getUserFromLine(Portal portal, String[] fields, TreeSet<ExtraUserdataField> extraFields)
	{
	  User user = new User(portal,fields[0].trim());
	  user.setFirstname(fields[1].trim());
	  user.setLastname(fields[2].trim());
	  user.setLastname2(fields[3].trim());
	  user.setEmail(fields[4].trim());
	  int i = 6; //5 es la contraseña.
	  Set<ExtraUserdata> extraUserdata = new HashSet<ExtraUserdata>();
	  for(ExtraUserdataField field: extraFields)
	    if (fields.length>i)
	      extraUserdata.add(new ExtraUserdata(field,user,fields[i++].trim()));
	  //user.setExtraUserdata(extraUserdata); // No es necesario por que paso user como argumento al constructor
		return user;
	}
	public ActionForward importUsersErrors(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{ //TODO Premium
		try
		{
			UserSessionSBean userSession=getUserSession(request);
			response.setContentType("text/plain"); 
			response.setHeader("Content-disposition", "attachment;filename="+userSession.getPortalid()+"_errors.txt");
			write(new BufferedReader(new StringReader((String)request.getSession().getAttribute("importUsersErrors"))),response);
			request.getSession().removeAttribute("importUsersErrors");
			return null;
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
			saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
	}
	public ActionForward exportUsers(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{ //TODO Premium
		try
		{
			UserSessionSBean userSession=getUserSession(request);
			response.setContentType("text/plain"); 
			response.setHeader("Content-disposition", "attachment;filename="+userSession.getPortalid()+"_users.csv"); 
			write(new BufferedReader(new StringReader(usermanager.getUsersAsCSV(userSession.getPortalid()))),response);
			return null;
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
			saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
	}
	public ActionForward roles(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{
		try
		{
		  return mapping.findForward("roles");
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
			saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
	}
	public ActionForward removeRoles(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{
		try
		{
		  UserSessionSBean userSession = getUserSession(request);
			for (String id: request.getParameterValues("id"))
				usermanager.removeRole(userSession.getPortalid(),new Integer(id));
			userSession.refresh(portalmanager.getPortal(userSession.getPortalid()));
			return roles(mapping,form,request,response);
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
			saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
	}
	public ActionForward usersByRoleId(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
	{
		try
		{
			UsersActionForm usersForm = (UsersActionForm)form;
			UserSessionSBean userSession=getUserSession(request);
			request.getSession().setAttribute("users",usermanager.getUsersByRoleIds(userSession.getPortalid(),usersForm.getRoleId()));
			return mapping.findForward("success");
		} catch (Throwable e)
		{
			log.error(e.getMessage(), e);
			saveErrors(request,getErrorsFromException(e));
			return mapping.findForward("error");
		}
	}
}
